/**
 * 
 * Copyright (C) 2011 Cody Stoutenburg . All rights reserved.
 *
 *       This program is free software; you can redistribute it and/or
 *       modify it under the terms of the GNU Lesser General Public License
 *       as published by the Free Software Foundation; either version 2.1
 *       of the License, or (at your option) any later version.
 *
 *       This program is distributed in the hope that it will be useful,
 *       but WITHOUT ANY WARRANTY; without even the implied warranty of
 *       MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 *       GNU Lesser General Public License for more details.
 *
 *       You should have received a copy of the GNU Lesser General Public License
 *       along with this program; if not, write to the Free Software
 *       Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA. 
 * 
 */
package ca.usherbrooke.mainApp.view.openSimulation;

import jade.core.AID;
import jade.core.behaviours.Behaviour;

import java.awt.BorderLayout;
import java.awt.FlowLayout;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.io.File;
import java.io.IOException;
import java.util.Map;

import javax.swing.JButton;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.JProgressBar;

import ca.usherbrooke.behaviours.config.RequestWorldModelBehaviour;
import ca.usherbrooke.behaviours.config.RequestWorldModelBehaviour.IWorldCallBack;
import ca.usherbrooke.mainApp.MainAppAgent;
import ca.usherbrooke.model.entity.IEntityModel;
import ca.usherbrooke.model.world.IWorldModel;

/**
 * @author Cody Stoutenburg
 * 
 */
public class PanelOpenSimulation extends JPanel {
	private static final long serialVersionUID = 1L;

	private final MainAppAgent agent;
	private final JPanel panelCenter;
	private PanelMapAgentEntity panelMapAgentEntity;

	private final AID worldAgent;
	private AID goalAgent;

	public PanelOpenSimulation(MainAppAgent agent, File simulationDirectory)
			throws IOException {
		this.setLayout(new BorderLayout());

		this.agent = agent;

		Object[] args = new Object[1];
		args[0] = simulationDirectory.getCanonicalPath() + "/properties.txt";
		// start the world agent
		worldAgent = this.agent.startAgent("worldUpdater",
				"ca.usherbrooke.agent.world.WorldAgentStandard", args);

		panelCenter = new JPanel(new FlowLayout());
		JProgressBar loadWorld = new JProgressBar();
		loadWorld.setIndeterminate(true);

		panelCenter.add(new JLabel("Loading simulation"));
		panelCenter.add(loadWorld);

		this.add(panelCenter, BorderLayout.CENTER);

		// do it last to be sure the constructor is finish
		Behaviour requestWorld = new RequestWorldModelBehaviour(agent,
				worldAgent, new IWorldCallBack() {
					@Override
					public void worldReceived(IWorldModel world) {
						onWorldModelLoad(world);
					}
				});
		agent.addBehaviour(requestWorld);
	}

	private void onWorldModelLoad(IWorldModel world) {
		Object[] args = new Object[1];
		args[0] = worldAgent;
		// ask the goal agent to start
		goalAgent = this.agent.startAgent("goals",
				"ca.usherbrooke.agent.goal.BasicGoalAgent", args);

		panelCenter.removeAll();
		panelCenter.validate();

		panelMapAgentEntity = new PanelMapAgentEntity(world);
		panelCenter.add(panelMapAgentEntity);

		JPanel panelSouth = new JPanel();
		JButton buttonStartSimulation = new JButton("Start simulation");
		buttonStartSimulation.addActionListener(new ActionListener() {
			@Override
			public void actionPerformed(ActionEvent e) {
				startSimulation();
			}
		});
		panelSouth.add(buttonStartSimulation);
		this.add(panelSouth, BorderLayout.SOUTH);
		panelCenter.revalidate();
		panelCenter.repaint();
	}

	private void startSimulation() {
		Object[] args;

		// start the viewer
		args = new Object[1];
		args[0] = worldAgent;
		this.agent.startAgent("viewer",
				"ca.usherbrooke.mainApp.WorldAgentViewer", args);

		Map<IEntityModel, String> allAgentEntity = this.panelMapAgentEntity
				.getAgentForEntities();

		// start all entities
		for (Map.Entry<IEntityModel, String> entity : allAgentEntity.entrySet()) {

			Long guid = entity.getKey().getGuid();
			args = new Object[4];
			args[0] = worldAgent;
			args[1] = goalAgent;
			args[2] = guid;
			args[3] = entity.getValue();

			this.agent.startAgent(guid.toString(),
					"ca.usherbrooke.agent.controller.BasicAgentLauncher", args);
		}

		// start goal
		args = new Object[2];
		args[0] = worldAgent;
		args[1] = goalAgent;
		this.agent.startAgent("goalBuilder",
				"ca.usherbrooke.mainApp.goal.GoalAgentBuilderViewer", args);

	}
}
